#include "stdafx.h"
#include "CppUnitTest.h"

#include <iostream>
#include <sstream>
#include <exception>
using namespace std;

#include "forwardList.h"

using namespace Microsoft::VisualStudio::CppUnitTestFramework;

namespace UnitTestForwardList
{		
	TEST_CLASS(UnitTest1)
	{
	public:
		forwardList<int> l;

		TEST_METHOD(TestEmpty)
		{
			// TODO: Your test code here
			Assert::AreEqual(true, l.isEmpty());
		}

		TEST_METHOD(TestPushFrontGetFront)
		{
			Assert::AreEqual(true, l.isEmpty());
			l.push_front(10);
			Assert::AreEqual(10, l.front());
			l.push_front(20);
			Assert::AreEqual(20, l.front());
			Assert::AreEqual(false, l.isEmpty());
		}

		TEST_METHOD(TestPopFront)
		{
			l.push_front(10);
			l.push_front(20);
			Assert::AreEqual(false, l.isEmpty());
			Assert::AreEqual(20, l.front());
			l.pop_front();
			Assert::AreEqual(10, l.front());
		}

		TEST_METHOD(TestClear)
		{
			l.push_front(10);
			l.push_front(20);
			l.push_front(30);
			l.clear();
			Assert::AreEqual(true, l.isEmpty());
		}

		TEST_METHOD(TestIterator)
		{
			l.push_front(10);
			l.push_front(20);
			forwardList<int>::iterator it(l.begin());
			Assert::AreEqual(20, it->getData());
			Assert::AreEqual(20, (*it).getData());
			it++;
			Assert::AreEqual(10, it->getData());
			l.push_front(30);

			char a[] = "0";
			for (auto it = l.begin(); it != l.end(); it++)
			{
				Logger::WriteMessage(a);
				a[0]++;
				
			}
		}

		TEST_METHOD(TestInsertAfter)
		{
			l.push_front(10);
			l.push_front(20);
			auto it(l.begin());
			it++;			
			l.insert_after(it, 30);
			Assert::AreEqual(10, it->getData());
			it++;
			Assert::AreEqual(30, it->getData());			
		}

	
		TEST_METHOD(TestCopyConstr)
		{			
			//forwardList<int> l;

			//ostringstream oss;
			l.push_front(10);
			l.push_front(20);
			l.push_front(30);
			forwardList<int> k(l);
			//oss << k.front() << ", " << l.front() << endl;
			//Logger::WriteMessage((oss.str().c_str()));
			//Assert::AreEqual(30, l.front());
			//k.pop_front();
			//Assert::AreEqual(20, k.front());
			//k.pop_front();
			//Assert::AreEqual(10, k.front());
			//k.pop_front();
			//Assert::AreEqual(true, k.isEmpty());			
		}

		TEST_METHOD(TestCopyAssign)
		{
			l.push_front(10);
			l.push_front(20);
			l.push_front(30);
			forwardList<int> k;
			k = l;
			Assert::AreEqual(30, k.front());
			Assert::AreEqual(k.front(), l.front());
		}

		TEST_METHOD(TestEraseAfter)
		{
			l.push_front(10);
			l.push_front(20);
			l.push_front(30);
			auto it(l.begin());		//30
			Assert::AreEqual(30, it->getData());
			l.erase_after(it);		//erase 20
			it++;					//10
			Assert::AreEqual(10, it->getData());
		}

		TEST_METHOD(TestSwapElements)
		{
			l.push_front(10);
			l.push_front(20);
			l.push_front(30);
			auto it(l.begin());	 //30
			auto it2(l.begin());						
			it2++;
			it2++;				//10
			Assert::AreEqual(30, it->getData());
			Assert::AreEqual(30, l.front());
			Assert::AreEqual(10, it2->getData());

			l.swap_elements(it, it2);
			Assert::AreEqual(30, it->getData());
			Assert::AreEqual(10, l.front());
			Assert::AreEqual(10, it2->getData());
		}

		TEST_METHOD(TestSwap)
		{
			forwardList<int> k;
			l.push_front(10);
			l.push_front(20);
			l.push_front(30);
			k.push_front(500);
			k.push_front(600);
			l.swap(k);
			Assert::AreEqual(600, l.front());
			l.pop_front();
			Assert::AreEqual(500, l.front());
			Assert::AreEqual(30, k.front());
			k.pop_front();
			Assert::AreEqual(20, k.front());
			k.pop_front();
			Assert::AreEqual(10, k.front());
		}
	};
}